import { db, models } from '../../db';

const { user: UserModel, user_hero: UserHeroModel, user_equip: UserEquipModel } = models;

export const roleUp = async (user_id: string, data: Record<string, any>) => {
  const transaction = await db.transaction();

  return new Promise(async (resolve, reject) => {
    try {
      const { id, position } = data;
      // 更新userHero表
      await UserHeroModel.update(
        { position_x: position[0], position_y: position[1] },
        {
          where: { user_id, id },
        },
      );
      await transaction.commit();
      resolve('ok');
    } catch (error) {
      console.log(error);
      await transaction.rollback();
    }
  });
};

export const roleDown = async (user_id: string, data: Record<string, any>) => {
  const transaction = await db.transaction();
  return new Promise(async (resolve, reject) => {
    try {
      const { id } = data;
      // 更新userHero表
      await UserHeroModel.update(
        { position_x: 0, position_y: 0 },
        {
          where: { user_id, id },
        },
      );
      await transaction.commit();
      resolve('ok');
    } catch (error) {
      console.log(error);
      await transaction.rollback();
    }
  });
};

export const roleChange = async (user_id: string, data: Record<string, any>) => {
  const transaction = await db.transaction();
  return new Promise(async (resolve, reject) => {
    try {
      const { id, position } = data;
      // 根据位置获取到旧的英雄
      const oldHero = await UserHeroModel.findOne({
        where: { user_id, position_x: position[0], position_y: position[1] },
        transaction,
      });

      // 根据id拿到新的英雄
      const newHero = await UserHeroModel.findOne({
        where: { id, user_id },
        transaction,
      });

      if (!oldHero || !newHero) {
        return reject('英雄不存在');
      }
      const {
        id: oldHeroId,
        position_x: oldX,
        position_y: oldY,
        equip1: oldEquip1,
        equip2: oldEquip2,
        equip3: oldEquip3,
        equip4: oldEquip4,
      } = oldHero.dataValues;
      const {
        id: newHeroId,
        position_x: newX,
        position_y: newY,
        equip1: newEquip1,
        equip2: newEquip2,
        equip3: newEquip3,
        equip4: newEquip4,
      } = newHero.dataValues;
      // 装备
      const oldHeroEquipIds = [oldEquip1, oldEquip2, oldEquip3, oldEquip4].filter(
        item => item !== null,
      );
      const newHeroEquipIds = [newEquip1, newEquip2, newEquip3, newEquip4].filter(
        item => item !== null,
      );
      // 换信息- 新英雄使用旧英雄的位置和装备
      await UserHeroModel.update(
        {
          position_x: oldX,
          position_y: oldY,
          equip1: oldEquip1,
          equip2: oldEquip2,
          equip3: oldEquip3,
          equip4: oldEquip4,
        },
        {
          where: { user_id, id: newHeroId },
          transaction,
        },
      );

      // 换信息- 旧英雄使用新英雄的位置和装备
      await UserHeroModel.update(
        {
          position_x: newX,
          position_y: newY,
          equip1: newEquip1,
          equip2: newEquip2,
          equip3: newEquip3,
          equip4: newEquip4,
        },
        {
          where: { user_id, id: oldHeroId },
          transaction,
        },
      );
      // 更新用户装备表
      await UserEquipModel.update(
        {
          hero_id: newHeroId,
        },
        {
          where: { user_id, id: oldHeroEquipIds },
          transaction,
        },
      );

      await UserEquipModel.update(
        {
          hero_id: oldHeroId,
        },
        {
          where: { user_id, id: newHeroEquipIds },
          transaction,
        },
      );

      await transaction.commit();
      resolve('ok');
    } catch (error) {
      console.log(error);
      await transaction.rollback();
    }
  });
};

export const roleEquipChange = async (user_id: string, data: Record<string, any>) => {
  const transaction = await db.transaction();
  return new Promise(async (resolve, reject) => {
    try {
      const { roleId, equipType, equipId } = data;
      const params: Record<string, any> = {};

      params[`equip${equipType}`] = equipId;

      const oldEquipIds = await UserHeroModel.findOne({
        where: { user_id, id: roleId },
      });

      const oldHeroId = await UserEquipModel.findOne({
        where: { user_id, id: equipId },
      });

      const oldEquipId = oldEquipIds?.dataValues[`equip${equipType}`];

      if (oldEquipId) {
        await UserEquipModel.update(
          {
            hero_id: null,
          },
          {
            where: { user_id, id: oldEquipId },
            transaction,
          },
        );
      }

      if (oldHeroId) {
        const newParams: Record<string, any> = {};
        newParams[`equip${equipType}`] = null;

        await UserHeroModel.update(newParams, {
          where: { user_id, id: oldHeroId.dataValues.hero_id },
          transaction,
        });
      }

      // 更新userHero表
      await UserHeroModel.update(params, {
        where: { user_id, id: roleId },
        transaction,
      });
      // 更新用户装备表
      await UserEquipModel.update(
        {
          hero_id: roleId,
        },
        {
          where: { user_id, id: equipId },
          transaction,
        },
      );

      await transaction.commit();
      resolve('ok');
    } catch (error) {
      console.log(error);
      await transaction.rollback();
    }
  });
};
